package com.example.dynamicdatasourcetest.aop;

import com.example.dynamicdatasourcetest.annotation.DataSource;
import com.example.dynamicdatasourcetest.datasource.DynamicDataSourceContextHolder;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Pointcut;
import org.aspectj.lang.reflect.MethodSignature;
import org.springframework.core.annotation.AnnotationUtils;
import org.springframework.stereotype.Component;

@Component
@Aspect
public class DataSourceAspect {
    @Pointcut("@annotation(com.example.dynamicdatasourcetest.annotation.DataSource) || @within(com.example.dynamicdatasourcetest.annotation.DataSource)")
    public void pc(){

    }

    @Around("pc()")
    public Object around(ProceedingJoinPoint proceedingJoinPoint){
        DataSource dataSource = getDataSource(proceedingJoinPoint);
        if (dataSource !=null){
            String value = dataSource.value();
            DynamicDataSourceContextHolder.setDataSourceType(value);
        }
        try {
            return proceedingJoinPoint.proceed();
        } catch (Throwable e) {
            e.printStackTrace();
        }finally {
            DynamicDataSourceContextHolder.clearDataSourceType();
        }
        return null;
    }

    private DataSource getDataSource(ProceedingJoinPoint proceedingJoinPoint) {
        MethodSignature signature = (MethodSignature) proceedingJoinPoint.getSignature();

        //方法上找
        DataSource annotation = AnnotationUtils.findAnnotation(signature.getMethod(), DataSource.class);
        if (annotation != null) {
            return annotation;
        }
        //类上找
        return AnnotationUtils.findAnnotation(signature.getDeclaringType(), DataSource.class);
    }
}
